﻿using System;
using MugenInjection.Delegates;

namespace MugenInjection.Interception.Interface
{
    /// <summary>
    /// Represents the factory for creating a proxy types.
    /// </summary>
    public interface IProxyFactory
    {
        /// <summary>
        /// Gets the <see cref="IProxyBuilder"/>.
        /// </summary>
        IProxyBuilder ProxyBuilder { get; }

        /// <summary>
        /// Creates a proxy based on the underlying type.
        /// </summary>
        /// <param name="baseType">The specified base type for proxy.</param>
        /// <param name="proxyType">The result proxy <see cref="Type"/>.</param>
        /// <returns>The specified <see cref="IProxyCollection"/> for intercept.</returns>
        Func<IProxyCollection> CreateProxy(Type baseType, out Type proxyType);

        /// <summary>
        /// Creates a proxy based on the underlying type and interfaces.
        /// </summary>
        /// <param name="baseType">The base type for proxy.</param>
        /// <param name="interfaces">The specified interfaces for proxy.</param>
        /// <param name="proxyType">The result proxy <see cref="Type"/>.</param>
        /// <returns>The <see cref="IProxyCollection"/> for intercept.</returns>
        Func<IProxyCollection> CreateProxy(Type baseType, Type[] interfaces, out Type proxyType);

        /// <summary>
        /// Creates a proxy based on interfaces.
        /// </summary>
        /// <param name="interfaces">The specified interfaces for proxy.</param>
        /// <param name="proxyType">The result proxy <see cref="Type"/>.</param>
        /// <returns><see cref="IProxyCollection"/> for intercept.</returns>
        Func<IProxyCollection> CreateProxy(Type[] interfaces, out Type proxyType);
    }
}